package edu.gwu.computerarchitecture.operation.execute;

import java.math.BigDecimal;
import java.text.DecimalFormat;
import java.util.ArrayList;

import edu.gwu.computerarchitecture.alu.ALU;
import edu.gwu.computerarchitecture.cpu.CPUUnits;
import edu.gwu.computerarchitecture.entity.Register;
import edu.gwu.computerarchitecture.entity.Register32Bits;
import edu.gwu.computerarchitecture.entity.WordType;
import edu.gwu.computerarchitecture.operation.Instruction;

/**
 * 
 * implement the execution of VADD instruction
 *
 * <p>detailed comment
 * @author Erzheng Dai 2013年12月7日
 * @see Execute
 * @since 1.0
 * @version 1.0
 */
public class ExecuteVADD extends Execute
{
    public ExecuteVADD(CPUUnits units, Instruction instr)
    {
        super(units, instr);
        // TODO Auto-generated constructor stub
    }
    /**
     * 
     * implement the VADD
     * 
     * @see edu.gwu.computerarchitecture.operation.execute.Execute#execute()
     */
    public void execute(){
        int addr_vector1 = 0;
        int addr_vector2 = 0;
        int vector_len = 0;
        float vector1 = 0;
        float vector2 = 0;
        int vector_result = 0;
        super.instruction.vector1_list = new ArrayList<String>();
		super.instruction.vector2_list = new ArrayList<String>();
		super.instruction.vector_result_list = new ArrayList<String>();
        Register rsr1 = rfRegister(instruction.rsr1);
        vector_len = rsr1.getRegister().getWord();
    	calculateEA();
    	addr_vector1 = cpuunits.mdr.getRegister().getWord();
    	super.instruction.address++;
    	calculateEA();
    	addr_vector2 = cpuunits.mdr.getRegister().getWord();
    	DecimalFormat fresult = new DecimalFormat("##0.00");    	
    	for(int i=0; i<vector_len; i++){    		
    		vector1 = Float.intBitsToFloat((cpuunits.memory.getMemory(addr_vector1+2*i) & 0xffff) | (cpuunits.memory.getMemory(addr_vector1+2*i+1) << 16));
    		super.instruction.vector1_list.add(fresult.format(vector1));
    		vector2 = Float.intBitsToFloat((cpuunits.memory.getMemory(addr_vector2+2*i) & 0xffff) | (cpuunits.memory.getMemory(addr_vector2+2*i+1) << 16));
    		super.instruction.vector2_list.add(fresult.format(vector2));
    		alu = new ALU(vector1, vector2, cpuunits);
    		alu.fadd();
    		super.instruction.vector_result_list.add(fresult.format(alu.getFResult()));
    		vector_result = Float.floatToIntBits(alu.getFResult());
    		cpuunits.memory.setMemory(addr_vector1+2*i, vector_result & 0xffff);
    		cpuunits.memory.setMemory(addr_vector1+2*i+1, vector_result >>> 16);
    	}       
    }
}